#include "ChatClient.h"
#include <QJsonArray>

ChatClient::ChatClient(QObject* parent)
    : QObject(parent), m_socket(new QTcpSocket(this)), m_isLoggedIn(false)
{
    connect(m_socket, &QTcpSocket::connected, this, &ChatClient::onConnected);
    connect(m_socket, &QTcpSocket::disconnected, this, &ChatClient::onDisconnected);
    connect(m_socket, &QTcpSocket::readyRead, this, &ChatClient::onReadyRead);
    connect(m_socket, &QTcpSocket::errorOccurred, this, &ChatClient::onErrorOccurred);
}

ChatClient::~ChatClient()
{
    disconnectFromServer();
}

void ChatClient::connectToServer(const QString& host, quint16 port)
{
    m_socket->connectToHost(host, port);
}

void ChatClient::disconnectFromServer()
{
    m_socket->disconnectFromHost();
    m_isLoggedIn = false;
}

void ChatClient::login(const QString& username, const QString& password)
{
    if (!m_socket->isOpen()) {
        emit loginFailed("未连接到服务器");
        return;
    }

    QJsonObject loginMsg;
    loginMsg["type"] = "login";
    loginMsg["username"] = username;
    loginMsg["password"] = password;

    QJsonDocument doc(loginMsg);
    m_socket->write(doc.toJson(QJsonDocument::Compact) + "\n");
}

void ChatClient::sendMessage(const model::Message& message)
{
    if (!m_isLoggedIn || !m_socket->isOpen()) {
        return;
    }

    QJsonObject msgObj;
    msgObj["type"] = "chat_message";
    msgObj["message_id"] = message.messageId;
    msgObj["session_id"] = message.chatSessionId;
    msgObj["content"] = QString::fromUtf8(message.content);
    msgObj["timestamp"] = message.time;

    QJsonDocument doc(msgObj);
    m_socket->write(doc.toJson(QJsonDocument::Compact) + "\n");
}

bool ChatClient::isConnected() const
{
    return m_socket->state() == QAbstractSocket::ConnectedState;
}

void ChatClient::onConnected()
{
    emit connected();
}

void ChatClient::onDisconnected()
{
    m_isLoggedIn = false;
    emit disconnected();
}

void ChatClient::onReadyRead()
{
    while (m_socket->canReadLine()) {
        QByteArray data = m_socket->readLine().trimmed();
        if (!data.isEmpty()) {
            processData(data);
        }
    }
}

void ChatClient::onErrorOccurred(QAbstractSocket::SocketError error)
{
    emit errorOccurred(m_socket->errorString());
}

void ChatClient::processData(const QByteArray& data)
{
    QJsonParseError parseError;
    QJsonDocument doc = QJsonDocument::fromJson(data, &parseError);

    if (parseError.error != QJsonParseError::NoError) {
        return;
    }

    QJsonObject json = doc.object();
    QString type = json["type"].toString();

    if (type == "login_response") {
        processLoginResponse(json);
    }
    else if (type == "chat_message") {
        processChatMessage(json);
    }
}

void ChatClient::processLoginResponse(const QJsonObject& json)
{
    bool success = json["success"].toBool();

    if (success) {
        model::UserInfo userInfo;
        userInfo.userId = json["user_id"].toString();
        userInfo.nickname = json["nickname"].toString();

        m_isLoggedIn = true;
        m_currentUser = userInfo.userId;
        emit loginSuccess(userInfo);
    }
    else {
        QString reason = json["reason"].toString("未知错误");
        emit loginFailed(reason);
    }
}

void ChatClient::processChatMessage(const QJsonObject& json)
{
    model::Message message;
    message.messageId = json["message_id"].toString();
    message.chatSessionId = json["session_id"].toString();
    message.content = json["content"].toString().toUtf8();
    message.time = json["timestamp"].toString();

    // 设置发送者信息
    QJsonObject senderObj = json["sender"].toObject();
    message.sender.userId = senderObj["user_id"].toString();
    message.sender.nickname = senderObj["nickname"].toString();

    emit messageReceived(message);
}
